﻿

using AudioStudio;
using AudioStudio.Components;
using AudioStudio.Tools;
using GameFramework.Battle.Core;
using System;
using System.Collections.Generic;
using UnityEngine;
using Yoozoo.Mars.Got;

namespace Yoozoo.Gameplay.RTS
{
    class SquareModel : IModel
    {
        private int _index;
        private GameObject _gameObject;
        private Transform _transform;
        private float _animatorSpeed = 1;
        public int index { get => _index; set => _index = value; }
        public GameObject GameObject { get => _gameObject; set => _gameObject = value; }
        public Transform Transform { get => _transform; set => _transform = value; }
        public float animatorSpeed { get => _animatorSpeed; set => _animatorSpeed = value; }
        private bool foververAttackSpeed = false;
        private Animator animator;
        protected Vector3 targetForward;
        protected Vector3 currentForward;
        protected float needTime = 0;
        private float rotateSpeed = 40f;
        protected float startTime;
        private int status;
        private bool isInBattle = false;
        public AudioEmitter3D audioEmitter;
        private bool isDeading = false;
        private GameObject defaultAperture;
        internal void Init(AudioEmitter3D emitter3D)
        {
            audioEmitter = emitter3D;
            animator = _gameObject.GetComponentInChildren<Animator>();
            currentForward = _gameObject.transform.forward;
            if (animator != null)   
            {
                animator.SetFloat("AttackSpeed", 1);
                animator.SetBool("IsInBattle", false);
            }
            foververAttackSpeed = false;
            isDeading = false;
        }

        public void OnUpdate()
        {
            if (startTime != default)
            {
                if (_gameObject!=null)
                {
                    if (Time.time - startTime < needTime)
                    {
                        _gameObject.transform.forward = Vector3.Lerp(currentForward, targetForward, (Time.time - startTime) / needTime);
                    }
                    else
                    {
                        _gameObject.transform.forward = targetForward;
                        startTime = default;
                        currentForward = targetForward;
                        PlayCurrentStatusAnimation(status);
                    }
                }
            }
        }
        public void setDefaultAperture(GameObject _defaultAperture)
        {
            defaultAperture = _defaultAperture;
        }
        
        public GameObject getDefaultAperture()
        {
            return defaultAperture;
        }

        public Transform Get(string name)
        {
            throw new System.NotImplementedException();
        }

        public T Get<T>() where T : Component
        {
            throw new System.NotImplementedException();
        }

        public float GetAnimationLength(string aniName, float delValue = 0.1F)
        {
            throw new System.NotImplementedException();
        }

        public float GetAnimatorTime(EAnimationType anim)
        {
            throw new System.NotImplementedException();
        }

        public Vector3 GetForward()
        {
            throw new System.NotImplementedException();
        }

        public Vector3 GetRotation()
        {
            throw new System.NotImplementedException();
        }

        public void Gets<T>(ref List<T> list) where T : Component
        {
            throw new System.NotImplementedException();
        }

        public void HideShadow()
        {
            throw new System.NotImplementedException();
        }

        public int InstanceID()
        {
            throw new System.NotImplementedException();
        }

        public void OnCreate()
        {
            throw new System.NotImplementedException();
        }

        public void OnFree()
        {
            throw new System.NotImplementedException();
        }

        
        public void OnUse()
        {
            throw new System.NotImplementedException();
        }

        public void ResetScale()
        {
            throw new System.NotImplementedException();
        }

        public void SetAlpha(float alpha)
        {
            if (alpha == 0)
            {
                GameObject?.SetActive(false);
            }
            if (alpha == 1)
            {
                GameObject.SetActive(true);
            }
        }

        public void SetAnimatorEnabled(bool active)
        {
            throw new System.NotImplementedException();
        }

        public void SetAnimatorSpeed(float speed)
        {
            throw new System.NotImplementedException();
        }

        public void SetAnimatorTrigger(EAnimationType trigger, bool isReplay, float playSpeed = 1)
        {
            throw new System.NotImplementedException();
        }

        public void SetCampColor(Color color)
        {
            throw new System.NotImplementedException();
        }

        public virtual void SetForward(Vector3 forward)
        {
            if (forward.normalized == currentForward.normalized)
            {
                return;
            }
            animator.ResetTrigger("Attack");
            PlayAnimation("Turn");
            targetForward = forward.normalized;
            startTime = Time.time;
            needTime = Vector3.Angle(targetForward, currentForward.normalized) / rotateSpeed;
            //if (_gameObject!=null)
            //{
            //    _gameObject.transform.forward = forward;
            //}
        }

        public void SetLayer(int layer)
        {
            throw new System.NotImplementedException();
        }

        public void SetPosition(Vector3 position)
        {
            if (_gameObject!=null)
            {
                _gameObject.transform.position = position;
            }
        }

        public void SetRotation(Vector3 rotation)
        {
            throw new System.NotImplementedException();
        }

        public void SetScale(float localScale, float shadowScale = 0)
        {
            throw new System.NotImplementedException();
        }

        public void SetShadowPosition()
        {
            throw new System.NotImplementedException();
        }

        public void SharedRim(Color color)
        {
            throw new System.NotImplementedException();
        }

        public void PlayAnimation(string animation)
        {
            if (isDeading)
            {
                return;
            }
            if (animator!=null)
            {
                animator.SetTrigger(animation);
            }
        }

        public void Dispose()
        {
            if (_gameObject != null)
            {
                GameObject.Destroy(_gameObject);
                _gameObject = null;
            }
            _transform = null;
            Timers.inst.Remove(PlayEffect);
            if (effectObj!=null)
            {
                GameObject.Destroy(effectObj);
            }
            if (audioEmitter!=null)
            {
                audioEmitter = null;
            }
        }

        internal void SetSquareStatus(int status)
        {
            if (this.status!=status && startTime == default)
            {
                PlayCurrentStatusAnimation(status);
            }
            this.status = status;
        }

        private void PlayCurrentStatusAnimation(int status)
        {
            if (isDeading)
            {
                return;
            }
            switch (status)
            {
                case 0:
                    PlayAnimation("Idle");//idle
                    break;
                case 1:
                    PlayAnimation("Idle");//move
                    break;
                case 2:
                    PlayAnimation("Attack");//idle
                    break;
                case 3:
                    PlayAnimation("Dead");//idle
                    break;
                case 7:
                    PlayAnimation("Attack");//idle
                    break;
                default:
                    break;
            }
        }

        internal void Death()
        {
            PlayAnimation("Dead");
            isDeading = true;
            OnDead();
        }
        
        protected virtual void OnDead()
        {
            //播特效
            Timers.inst.Add(0.6f,1,PlayEffect);
        }
        
        private GameObject effectObj;
        private void PlayEffect(object param)
        {
            var resMgr = ArmyManager.Instance.GetRtsResourceManager();
            if (resMgr!=null)
            {
                resMgr.LoadBossDeadEffect((effectObj) =>
                {
                    this.effectObj = effectObj;
                    if (GameObject!=null)
                    {
                        effectObj.transform.position = GameObject.transform.position;
                        if (audioEmitter!=null)
                        {
                            AudioManager.PlaySound("sfx_rts_leaguemonster_death", audioEmitter.gameObject, AudioTriggerSource.EffectSound);
                        }
                    }
                });
            }
        }

        internal void SetAttackAnimationSpeed(float animationSpeed, float speedTime)
        {
            if (animator!=null)
            {
                Timers.inst.Remove(SetAttackSpeedNormal);
                animator.SetFloat("AttackSpeed", animationSpeed);
                if (speedTime == -1) //一直加速
                {
                    foververAttackSpeed = true;
                }
                else
                {
                    Timers.inst.Add(speedTime, 1, SetAttackSpeedNormal);
                }
            }
        }

        public void SetModelVisible(bool active)
        {
            if (GameObject!=null)
            {
                GameObject.SetActive(active);
            }
        }

        private void SetAttackSpeedNormal(object obj)
        {
            if (animator != null && !foververAttackSpeed)
            {
                animator.SetFloat("AttackSpeed", 1);
            }
        }


        internal void SetIsInBattle(bool isInBattle)
        {
            if (this.isInBattle!= isInBattle)
            {
                this.isInBattle = isInBattle;
                animator?.SetBool("IsInBattle", isInBattle);
            }
        }
    }
}
